package com.aboverock.module.shiro.realms;

import com.aboverock.autoconfigure.util.JwtUtil;
import com.aboverock.common.enums.UserStatusEnum;
import com.aboverock.core.token.TokenLoginToken;
import com.aboverock.module.system.domain.User;
import com.aboverock.module.system.service.UserRoleService;
import com.aboverock.module.system.service.UserService;
import com.aboverock.module.system.utils.UserInfoUtil;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.JwtException;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.LockedAccountException;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;

/**
 * 使用token登录另一系统时认证.
 * 
 * @author Rock Wang
 *
 */
public class LoginTokenShiroRealm extends AuthorizingRealm {
    private Logger logger = LoggerFactory.getLogger(getClass());

    @Autowired
    @Lazy
    private UserService userService;

    // @Autowired
    // @Lazy
    // private DatalakeService datalakeService;

    @Autowired
    @Lazy
    private UserRoleService userRoleService;

    @Override
    public boolean supports(AuthenticationToken token) {
        return token instanceof TokenLoginToken;
    }

    public LoginTokenShiroRealm() {
        setAuthorizationCachingEnabled(false);
    }

    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        return null;
    }

    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        String jwt = token.getPrincipal().toString();
        Claims claims;
        try {
            claims = JwtUtil.getClaimByToken(jwt);
        } catch (JwtException e) {
            throw new AuthenticationException(e);
        }

        String loginName = claims.getSubject();
        if (UserInfoUtil.isSuperAdminName(loginName)) {
            return new SimpleAuthenticationInfo(loginName, Boolean.TRUE, getName());
        }

        User user = userService.getADUserByLoginName(loginName);
        if (user != null && user.getStatus().equals(UserStatusEnum.LOCKED.getValue())) {
            throw new LockedAccountException(loginName + "'s account is locked");
        } else if (null == user) {
            // try {
            //     user = datalakeService.getUserByLoginName(loginName);
            // } catch (DatalakeRequestException | DatalakeDataParseException e) {
            //     logger.warn("Data-Smart: 从数据湖获取用户{}信息失败", loginName, e);
            // }

            // 从数据湖获取用户信息失败
            if (null == user) {
                user = new User();
            }

            user.setLoginName(loginName);
            if (StringUtils.isBlank(user.getName())) {
                user.setName(loginName);
            }
            // 设置创建与更新用户
            user.setCreateUser(loginName);
            user.setUpdateUser(loginName);
            User newUser = userService.saveDataLakeEmpInfoToDb(user);
            if (null != newUser) {
                if (!userRoleService.addCommonRole(newUser.getId())) {
                    logger.warn("Data-Smart: 给用户{}添加通用角色失败", newUser.getLoginName());
                }
            }
        }

        return new SimpleAuthenticationInfo(loginName, Boolean.TRUE, getName());
    }

}
